//
//  MDHNavigationControllerStack.m
//  JSTech
//
//  Created by 高得华 on 2019/4/25.
//  Copyright © 2020 华&梅. All rights reserved.
//

#import "MDHNavigationControllerStack.h"
#import "MDHNavigationController.h"
#import "MDHTabBarController.h"
#import "MDHRouter.h"

@interface MDHNavigationControllerStack ()

@property (nonatomic, strong) id<MDHViewModelServices> services;
@property (nonatomic, strong) NSMutableArray *navigationControllers;

@end


@implementation MDHNavigationControllerStack

- (instancetype)initWithServices:(id<MDHViewModelServices>)services {
    self = [super init];
    if (self) {
        self.services = services;
        self.navigationControllers = [[NSMutableArray alloc] init];
        [self registerNavigationHooks];
    }
    return self;
}

- (void)pushNavigationController:(UINavigationController *)navigationController {
    if ([self.navigationControllers containsObject:navigationController]) return;
    [self.navigationControllers addObject:navigationController];
}

- (UINavigationController *)popNavigationController {
    UINavigationController *navigationController = self.navigationControllers.lastObject;
    [self.navigationControllers removeLastObject];
    return navigationController;
}

- (UINavigationController *)topNavigationController {
    return self.navigationControllers.lastObject;
}

/// Retrieves the top viewcontroller in the stack.
///
/// Returns the top viewcontroller in the stack.
- (UIViewController *)topViewController {
    return self.topNavigationController.topViewController;
}

- (void)registerNavigationHooks {
    @weakify(self)
    [[(MDHViewModelServicesImpl *)self.services
      rac_signalForSelector:@selector(pushViewModel:animated:)]
     subscribeNext:^(RACTuple *tuple) {
         @strongify(self)
        UIViewController *viewController = (UIViewController *)[MDHRouter.sharedInstance viewControllerForViewModel:tuple.first];
        [self.services pushViewController:viewController animated:[tuple.second boolValue]];
     }];
    
    [[(MDHViewModelServicesImpl *)self.services
      rac_signalForSelector:@selector(popViewModelAnimated:)]
     subscribeNext:^(RACTuple *tuple) {
         @strongify(self)
         [self.navigationControllers.lastObject popViewControllerAnimated:[tuple.first boolValue]];
     }];
    
    [[(MDHViewModelServicesImpl *)self.services
      rac_signalForSelector:@selector(popToRootViewModelAnimated:)]
     subscribeNext:^(RACTuple *tuple) {
         @strongify(self)
         [self.navigationControllers.lastObject popToRootViewControllerAnimated:[tuple.first boolValue]];
     }];
    
    [[(MDHViewModelServicesImpl *)self.services
      rac_signalForSelector:@selector(presentViewModel:animated:completion:)]
     subscribeNext:^(RACTuple *tuple) {
         @strongify(self)
         UIViewController *viewController = (UIViewController *)[MDHRouter.sharedInstance viewControllerForViewModel:tuple.first];
         
         UINavigationController *presentingViewController = self.navigationControllers.lastObject;
         if (![viewController isKindOfClass:UINavigationController.class]) {
             viewController = [[MDHNavigationController alloc] initWithRootViewController:viewController];
         }
         [self pushNavigationController:(UINavigationController *)viewController];
         viewController.modalPresentationStyle = UIModalPresentationOverFullScreen;
         [presentingViewController presentViewController:viewController animated:[tuple.second boolValue] completion:tuple.third];
     }];
    
    [[(MDHViewModelServicesImpl *)self.services
      rac_signalForSelector:@selector(dismissViewModelAnimated:completion:)]
     subscribeNext:^(RACTuple *tuple) {
         @strongify(self)
         [self popNavigationController];
         [self.navigationControllers.lastObject dismissViewControllerAnimated:[tuple.first boolValue] completion:tuple.second];
     }];
    
    [[(MDHViewModelServicesImpl *)self.services
      rac_signalForSelector:@selector(resetRootViewModel:)]
     subscribeNext:^(RACTuple *tuple) {
         @strongify(self)
        /// VM映射VC
        UIViewController *viewController = (UIViewController *)[MDHRouter.sharedInstance viewControllerForViewModel:tuple.first];
        [self.services resetRootViewController:viewController];
     }];
    
    ///设置跟视图
    /// Reset the corresponding view controller as the root view controller of the application's window.
    ///
    /// viewModel - the view model
    [[(MDHViewModelServicesImpl *)self.services
      rac_signalForSelector:@selector(resetRootViewController:)]
     subscribeNext:^(RACTuple *tuple) {
         @strongify(self)
         [self.navigationControllers removeAllObjects];
         /// VM映射VC
         UIViewController *viewController = (UIViewController *)tuple.first;
         if (![viewController isKindOfClass:[UINavigationController class]] &&
             ![viewController isKindOfClass:[MDHTabBarController class]]) {
             viewController = [[MDHNavigationController alloc] initWithRootViewController:viewController];
             [self pushNavigationController:(UINavigationController *)viewController];
         }
        if (self.window) {
            self.window.rootViewController = viewController;
        }else{
            DTLog(@"keyWindow: %@",[UIApplication sharedApplication].keyWindow);
            NSAssert(self.window, @"window 为空，请设置window属性");
        }
     }];
    
    ///跳转界面
    [[(MDHViewModelServicesImpl *)self.services
      rac_signalForSelector:@selector(pushViewController:animated:)]
     subscribeNext:^(RACTuple *tuple) {
         @strongify(self)
         MDHViewController *topViewController = (MDHViewController *)[self.navigationControllers.lastObject topViewController];
         if (topViewController.tabBarController) {
             topViewController.snapshot = [topViewController.tabBarController.view snapshotViewAfterScreenUpdates:NO];
         } else {
             topViewController.snapshot = [[self.navigationControllers.lastObject view] snapshotViewAfterScreenUpdates:NO];
         }
         UIViewController *viewController = (UIViewController *)tuple.first;
         [self.navigationControllers.lastObject pushViewController:viewController animated:[tuple.second boolValue]];
    }];
}

@end
